package com.huiying.controller;


import com.huiying.constant.MessageConstant;
import com.huiying.entity.dto.CommentDTO;
import com.huiying.entity.dto.CommentPageDTO;
import com.huiying.entity.entity.Tag;
import com.huiying.entity.result.PageResult;
import com.huiying.entity.result.Result;
import com.huiying.service.CommonService;
import com.huiying.service.FileUrlService;
import com.huiying.utils.LocalFileUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.util.List;
import java.util.UUID;

/**
 * @Author: lsh
 * @Date: 2024/10/26/17:11
 * @Description: 文件上传接口
 */
@RestController
@RequestMapping("/user/common")
@Slf4j
@Api(tags = "通用接口")
public class CommonController {

    @Autowired
    private LocalFileUtil fileUtil;

    @Autowired
    private CommonService commonService;

    @Autowired
    private FileUrlService fileUrlService;


    /***
     * 文件上传
     * @param file 上传文件
     * @return: com.sky.result.Result<java.lang.String>
     */
    @PostMapping("/upload")
    @ApiOperation("文件上传")
    public Result<String> upload(MultipartFile file){
        log.info("文件上传: {}", file);

        // 1. 检查文件是否为空
        if (file == null || file.isEmpty()) {
            return Result.error(MessageConstant.UPLOAD_FAILED + ": 上传文件不能为空");
        }

        try {
            // 2. 获取原始文件名和文件扩展名
            String originalFilename = file.getOriginalFilename();
            String extension = "";
            if (originalFilename != null && originalFilename.contains(".")) {
                extension = originalFilename.substring(originalFilename.lastIndexOf("."));
            }

            // 3. 生成一个唯一的文件名用于本地存储
            String storedFileName = UUID.randomUUID().toString() + extension;

            // 4. 调用 LocalFileUtil 将文件上传到本地存储目录
            // LocalFileUtil.upload 方法现在应该返回的是这个存储后的文件名 (storedFileName)
            String uploadResultFileName = fileUtil.upload(file.getBytes(), storedFileName);

            // 5. 检查本地文件上传是否成功
            if (uploadResultFileName != null) {
                // 6. 使用 FileUrlService 拼接完整的、前端可访问的 URL
                String fullAccessUrl = fileUrlService.generateFileAccessUrl(uploadResultFileName);

                // 7. 返回成功结果，包含完整的 URL
                log.info("文件上传成功，可访问URL: {}", fullAccessUrl);
                return Result.success(fullAccessUrl);
            } else {
                // 文件存储失败，通常是写入本地目录时出错
                log.error("文件上传到本地失败，未返回文件名。");
                return Result.error(MessageConstant.UPLOAD_FAILED + ": 文件存储处理失败");
            }

        } catch (IOException e) {
            log.error("文件上传失败，IO异常: {}", e.getMessage(), e); // 打印详细异常信息
            return Result.error(MessageConstant.UPLOAD_FAILED + ": 文件读写异常 " + e.getMessage());
        } catch (Exception e) {
            log.error("文件上传发生未知异常: {}", e.getMessage(), e); // 捕获其他运行时异常
            return Result.error(MessageConstant.UPLOAD_FAILED + ": 未知错误 " + e.getMessage());
        }
    }

    /**
     *  查询标签列表
     * @return: com.fx.result.Result<java.util.List<com.fx.entity.Tag>>
     */
    @GetMapping("/getTags")
    @ApiOperation("获取标签列表")
    public Result<List<Tag>> getTags(){
        log.info("查询标签列表");
        List<Tag> tags = commonService.getTags();
        return Result.success(tags);
    }

    /**
     * 用户点赞
     * @param contentId 内容id
     * @param contentType 内容类型
     * @return: com.fx.result.Result
     */
    @PostMapping("/like")
    @ApiOperation("用户点赞")
    public Result like(Long contentId,String contentType){
        log.info("用户点赞");
        boolean isLike = commonService.like(contentId,contentType);
        return isLike ? Result.success():Result.error("点赞失败");
    }

    /**
     * 用户取消点赞
     * @param contentId 内容id
     * @param contentType 内容类型
     * @return: com.fx.result.Result
     */
    @DeleteMapping("/unLike")
    @ApiOperation("用户取消点赞")
    public Result unLike(Long contentId,String contentType){
        log.info("用户取消点赞");
        boolean isUnLike = commonService.unLike(contentId,contentType);
        return isUnLike ? Result.success():Result.error("用户未点赞，无法取消");
    }

    /**
     * 用户收藏内容（需求单或作品）
     * @param contentId 内容ID（需求单或作品的ID）
     * @param contentType 内容类型（DEMAND 或 WORK）
     * @return: com.fx.result.Result
     */
    @PostMapping("/collect")
    @ApiOperation("用户收藏内容")
    public Result collect(Long contentId,String contentType) {
        log.info("用户收藏内容: contentId={}, contentType={}", contentId, contentType);
        Boolean isCollect = commonService.collect(contentId, contentType);
        return isCollect ? Result.success("收藏成功") : Result.error("用户已收藏过该内容");
    }

    /**
     * 用户取消收藏内容（需求单或作品）
     * @param contentId 内容ID（需求单或作品的ID）
     * @param contentType 内容类型（DEMAND 或 WORK）
     * @return: com.fx.result.Result
     */
    @DeleteMapping("/uncollect")
    @ApiOperation("用户取消收藏内容")
    public Result unCollect(Long contentId,String contentType) {
        log.info("用户取消收藏内容: contentId={}, contentType={}", contentId, contentType);
        Boolean isUnCollect = commonService.unCollect(contentId, contentType);
        return isUnCollect ? Result.success("取消收藏成功") : Result.error("用户未收藏过该内容");
    }

    /**
     * 用户发布评论
     * @param commentDTO 评论数据传输类
     * @return: com.fx.result.Result
     */
    @PostMapping("/addComment")
    @ApiOperation("发表评论")
    public Result addComment(@RequestBody CommentDTO commentDTO) {
        log.info("{}",commentDTO.getContentType());
        log.info("用户发表评论");
        commonService.addComment(commentDTO);
        return Result.success();
    }

    /**
     * 评论分页查询
     * @param commentPageDTO 评论分页查询数据传输类
     * @return: com.fx.result.Result<com.fx.result.PageResult>
     */
    @GetMapping("/page")
    @ApiOperation("评论分页查询")
    public Result<PageResult> pageQuery(CommentPageDTO commentPageDTO){
        log.info("评论分页查询");
        PageResult result = commonService.pageQuery(commentPageDTO);
        return Result.success(result);
    }

    /**
     * 浏览记录分页查询
     * @param page
     * @param pageSize
     * @return: com.fx.result.Result<com.fx.result.PageResult>
     */
    @GetMapping("/view")
    @ApiOperation("浏览记录分页查询")
    public Result<PageResult> getViewList(Integer page,Integer pageSize,String contentType){
        log.info("浏览记录分页查询");

        PageResult pageResult = commonService.getViewList(page,pageSize,contentType);

        return Result.success(pageResult);
    }

    @GetMapping("/getCollectList")
    @ApiOperation("查看用户收藏列表")
    public Result getFavoritesList( Integer page, Integer pageSize, String contentType) {
        log.info("查看用户收藏列表");
        PageResult result = commonService.getCollectList(page, pageSize, contentType);
        return Result.success(result);
    }
}